/*
  ******************************************************************************
  * @file    pdm_demo.c
  * @author  FreqChip Firmware Team
  * @version V1.0.0
  * @date    2021
  * @brief   PDM module Demo.
  ******************************************************************************
  * @attention
  *
  * Copyright (c) 2021 FreqChip.
  * All rights reserved.
  ******************************************************************************
*/
#include "pdm_demo.h"

#include "driver_gpio.h"
#include "driver_pmu.h"
#include "driver_pdm.h"
#include "driver_uart_ex.h"

#include "co_printf.h"
#include "co_log.h"

#include "ble_stack.h"

GPIO_InitTypeDef  GPIO_Handle;
PDM_HandleTypeDef PDM_Handle;

// 本demo以16K采样率为例

// 16000K采样速率，1秒产生16000个音频数据，1ms产生 16个音频数据。
// 开辟一个可容纳10ms音频数据的Buffer，循环使用。
uint16_t PDM_Buffer[16 * 10];
uint16_t ReadCount;

void PDM_Threshold_Full_callback(PDM_HandleTypeDef *hpdm)
{
    ReadCount += 16;
    if (ReadCount >= 160)
    {
        ReadCount = 0;
    }
    hpdm->p_RxData = &PDM_Buffer[ReadCount];
}

/************************************************************************************
 * @fn      pdm_demo
 *
 * @brief   pdm demo
 *
 * @param   fe_Demo: demo select. 
 */
void pdm_demo(enum_PDM_Demo_t fe_Demo)
{
    /* IP Clock enable */
    __SYSTEM_GPIO_CLK_ENABLE();
    __SYSTEM_PDM_CLK_ENABLE();

    switch (fe_Demo)
    {
        case PDM_QUERY_MODE:
        {
            co_printf("PDM demo: Query Mode \r\n");

            ReadCount = 0;

            PDM_Handle.Init.SamplingEdge   = SAMPLING_RISING_EDGE;
            PDM_Handle.Init.SamplingRate   = SAMPLING_RATE_16000;
            PDM_Handle.Init.FIFO_Threshold = 16;
            pdm_init(&PDM_Handle);

            /* default volume is 370 */
            /* User can config volume++ or volume-- */
            pdm_set_volume(500);

            pdm_enable();

            while(1)
            {
                /* PDM FIFO Threshold FULL  */
                if (__PDM_IS_FIFO_THRESHOLD_FULL())
                {
                    pdm_read_data(&PDM_Buffer[ReadCount], PDM_Handle.Init.FIFO_Threshold);

                    ReadCount += 16;
                    if (ReadCount >= 160)
                    {
                        ReadCount = 0;
                    }
                }
            }
        }

        case PDM_INT_MODE:
        {
            co_printf("PDM demo: interrupt Mode \r\n");

            ReadCount = 0;

            PDM_Handle.Init.SamplingEdge = SAMPLING_RISING_EDGE;
            PDM_Handle.Init.SamplingRate = SAMPLING_RATE_16000;
            PDM_Handle.Init.FIFO_Threshold = 16;
            PDM_Handle.FIFOTHFullCallback  = PDM_Threshold_Full_callback;
            pdm_init(&PDM_Handle);

            pdm_read_data_IT(&PDM_Handle, PDM_Buffer);
            NVIC_EnableIRQ(PDM_IRQn);

            pdm_enable();
        }break;

        default:break;
    }

    while(1);
}

/************************************************************************************
 * @fn      pdm_isr
 *
 * @brief   pdm interrupt handler
 */
__attribute__((section("ram_code"))) void pdm_isr(void)
{
    pdm_IRQHandler(&PDM_Handle);
}
